const APIError = require('../../rest_api').APIError;
const { CommentsModel, CommentsChildrenModel } = require('../../db/index');
const { isLogin } = require('../lib'); // 验证登录

module.exports = {
    //  添加文章评论
    'POST /api/v1/comment': async (ctx, next) => {
        const body = ctx.request.body;
        const content = body.content.trim();
        const token = ctx.headers.token;
        const article_id = body.article_id;

        // 验证评论内容
        if (content.length === 0) {
            throw new APIError('internal:comment_content_error', '评论内容不能为空');
        }
        // 验证登录
        let login;
        try {
            login = await isLogin(token, true);
        } catch (error) {
            throw new APIError(error.code, error.message);
        }

        const authId = login.id;

        // 参数
        const Comments = new CommentsModel({
            content,
            article: article_id,
            auth: login.id
        });
        try {
            const data = await Comments.save();
            // 返回数据
            ctx.rest({
                message: '评论成功',
                data
            });
        } catch (error) {
            console.log(error);
            throw new APIError('internal:comment_error', '评论失败');
        }
        await next();
    },
    //  回复评论或@人
    'POST /api/v1/comment_children': async (ctx, next) => {
        const body = ctx.request.body;
        const token = ctx.headers.token;
        const content = body.content.trim();        // 评论内容
        const parent_id = body.parent_id;           // 父级评论id
        const parent_auth = body.parent_auth;       // 父级评论作者id
        const reply = body.reply;                   // 被@的人

        // 验证评论内容
        if (content.length === 0) {
            throw new APIError('internal:comment_children_content_error', '评论内容不能为空');
        }

        // 验证登录
        let login;
        try {
            login = await isLogin(token, true);
        } catch (error) {
            throw new APIError(error.code, error.message);
        }
        const authId = login.id;

        // 验证父评论是否存在或是否已被删除
        const parentQuery = await CommentsModel.findById(parent_id);
        if (parentQuery === null) {
            throw new APIError('internal:comment_error', '此评论不存在，评论失败');
        }
        if (parentQuery.delete) {
            throw new APIError('internal:comment_error', '此评论已被删除，评论失败');
        }

        // 写入数据库
        try {
            let data;
            if (parent_auth) {
                // 给父评论作者发消息
                data = await CommentsChildrenModel.create({
                    content,
                    auth: authId,
                    parent_id,
                    parent_auth
                });
            } else if (reply) {
                // 给父评论作者发消息 给被@者发消息
                data = await CommentsChildrenModel.create({
                    content,
                    auth: authId,
                    parent_id,
                    reply
                });
            }
            // 父评论关联子评论
            CommentsModel.findByIdAndUpdate(parent_id, {
                $push: {
                    children: data.id
                },
                $set: {
                    upDate: new Date()
                }
            });
            // 返回数据
            ctx.rest({
                message: '评论成功',
                data
            });
        } catch (error) {
            console.log(error);
            throw new APIError('internal:comment_error', '评论失败');
        }
        await next();
    },
    //  获取评论列表
    'GET /api/v1/comment': async (ctx, next) => {
        let body = ctx.query;
        // 传入参数
        let count = parseFloat(body.count) || 10;
        let page = parseFloat(body.page) - 1 || 0;
        const article_id = body.article_id;

        // 查询条件
        let conditions = {
            article: article_id,
            delete: false
        };
        // 显示参数
        let needKey = {
            content: 1,
            article: 1,
            auth: 1,
            upDate: 1
        };

        try {
            const pop = {
                path: 'auth',
                select: '_id cname headImg'
            };

            const dataCount = await CommentsModel.find(conditions, needKey).count();
            const data = await CommentsModel.find(conditions, needKey)
                .sort({ upDate: -1 })
                .populate(pop)
                .limit(count)
                .skip(page * count);

            // 返回数据
            ctx.rest({
                data,
                count: dataCount,
                page: page + 1
            });
        } catch (error) {
            throw new APIError('internal:comment_list_error', '获取评论列表失败');
        }

        await next();
    },
    //  获取子评论列表
    'GET /api/v1/comment_children': async (ctx, next) => {
        let body = ctx.query;
        // 传入参数
        let count = parseFloat(body.count) || 10;
        let page = parseFloat(body.page) - 1 || 0;

        // 查询条件
        let conditions = {
            delete: false
        };
        // 显示参数
        let needKey = {
            content: 1,
            auth: 1,
            upDate: 1
        };

        try {
            const pop = {
                path: 'auth reply',
                select: '_id cname headImg'
            };

            const dataCount = await CommentsChildrenModel.count(conditions);
            const data = await CommentsChildrenModel.find(conditions, needKey)
                .sort({ upDate: -1 })
                .populate(pop)
                .limit(count)
                .skip(page * count);

            // 返回数据
            ctx.rest({
                data,
                count: dataCount,
                page: page + 1
            });
        } catch (error) {
            throw new APIError('internal:comment_list_error', '获取评论列表失败');
        }

        await next();
    },
    //  删除评论
    'DELETE /api/v1/comment': async (ctx, next) => {
        const body = ctx.request.body;
        const token = ctx.headers.token;
        const id = body.id;

        if (id.length === 0) {
            throw new APIError('internal:comment_contentType_error', '请传入评论ID');
        }
        //  获取评论信息
        const queryData = await CommentsModel.findById(id);
        // 判断是否已被删除
        if (queryData.delete) {
            throw new APIError('internal:comment_contentType_error', '此评论已被删除，请勿重复删除');
        }
        // 验证登录
        let login;
        try {
            // 验证是否为评论作者或者管理员
            login = await isLogin(token, true, ['超级管理员', '管理员'], queryData.auth);
        } catch (error) {
            throw new APIError(error.code, error.message);
        }
        // 当删除者不是本人时，需要传入删除原因，并通知被删除评论用户
        if (!login.isoneself) {

        }
        // 验证通过
        try {
            const data = await CommentsModel.findByIdAndUpdate(id, {
                delete: true,
                upDate: new Date()
            });
            CommentsChildrenModel.update({ parent_id: id }, {
                delete: true,
                upDate: new Date()
            }, { multi: true }).then(res => {
                console.log(`删除了${res.n}条子评论`);
            }).catch(err => {
                console.log('错误：', err)
            });
            // 返回数据
            ctx.rest({
                message: '删除成功'
            });
        } catch (error) {
            console.log(error);
            throw new APIError('internal:comment_error', '删除失败');
        }
        await next();
    },
    //  删除子评论
    'DELETE /api/v1/comment_children': async (ctx, next) => {
        const body = ctx.request.body;
        const token = ctx.headers.token;
        const id = body.id;

        if (id.length === 0) {
            throw new APIError('internal:comment_contentType_error', '请传入评论ID');
        }
        //  获取评论信息
        const queryData = await CommentsChildrenModel.findById(id);
        // 判断是否已被删除
        if (queryData.delete) {
            throw new APIError('internal:comment_contentType_error', '此评论已被删除，请勿重复删除');
        }
        // 验证登录
        let login;
        try {
            // 验证是否为评论作者或者管理员
            login = await isLogin(token, true, ['超级管理员', '管理员'], queryData.auth);
        } catch (error) {
            throw new APIError(error.code, error.message);
        }
        // 当删除者不是本人时，需要传入删除原因，并通知被删除评论用户
        if (!login.isoneself) {

        }
        // 验证通过
        try {
            const data = await CommentsChildrenModel.findByIdAndUpdate(id, {
                delete: true,
                upDate: new Date()
            });
            // 返回数据
            ctx.rest({
                message: '删除成功'
            });
        } catch (error) {
            console.log(error);
            throw new APIError('internal:comment_error', '删除失败');
        }
        await next();
    }
};
